﻿#include "builder.h"
#include <iostream>

void Product1::ListParts() const
{
    std::cout << "Product1 parts: ";
    for (size_t i = 0; i < parts_.size(); i++)
    {
        if (parts_[i] == parts_.back())
        {
            std::cout << parts_[i];
        }
        else
        {
            std::cout << parts_[i] << ", ";
        }
    }
    std::cout << "\n\n";
}

void Product2::ListParts() const
{
    std::cout << "Product2 parts: ";
    for (size_t i = 0; i < parts_.size(); i++)
    {
        if (parts_[i] == parts_.back())
        {
            std::cout << parts_[i];
        }
        else
        {
            std::cout << parts_[i] << ", ";
        }
    }
    std::cout << "\n\n";
}

ConcreteBuilder1::ConcreteBuilder1()
{
    this->reset();
}

ConcreteBuilder1::~ConcreteBuilder1()
{
    delete product;
}

void ConcreteBuilder1::reset()
{
    this->product = new Product1();
}

void ConcreteBuilder1::producePartA() const
{
    this->product->parts_.push_back("PartA1");
}

void ConcreteBuilder1::producePartB() const
{
    this->product->parts_.push_back("PartB1");
}

void ConcreteBuilder1::producePartC() const
{
    this->product->parts_.push_back("PartC1");
}

Product1 *ConcreteBuilder1::GetProduct()
{
    Product1 *result = this->product;
    this->reset();
    return result;
}

ConcreteBuilder2::ConcreteBuilder2()
{
    this->reset();
}

ConcreteBuilder2::~ConcreteBuilder2()
{
    delete product;
}

void ConcreteBuilder2::reset()
{
    this->product = new Product2();
}

void ConcreteBuilder2::producePartA() const
{
    this->product->parts_.push_back("PartA1");
}

void ConcreteBuilder2::producePartB() const
{
    this->product->parts_.push_back("PartB1");
}

void ConcreteBuilder2::producePartC() const
{
    this->product->parts_.push_back("PartC1");
}

Product2 *ConcreteBuilder2::GetProduct()
{
    Product2 *result = this->product;
    this->reset();
    return result;
}

void Director::set_builder(Builder *builder)
{
    this->builder = builder;
}

void Director::buildMinimalViableProduct()
{
    this->builder->producePartA();
}

void Director::buildFullFeaturedProduct()
{
    this->builder->producePartA();
    this->builder->producePartB();
    this->builder->producePartC();
}